<template>
    <div class="app-container">

        <el-row :gutter="10" class="mb5">
            <el-col :span="1.5">
                <el-button plain icon="el-icon-refresh-left" v-if="issql" size="mini" :disabled="multiple"
                    @click="batchRecover">批量恢复</el-button>
            </el-col>
            <el-col :span="1.5">
                <el-button plain icon="el-icon-download" size="mini" :disabled="multiple"
                    @click="batchDownload">批量下载</el-button>
            </el-col>
        </el-row>


        <el-table :height="tableHeight" border v-loading="loading" :data="recordList"
            @selection-change="handleSelectionChange">
            <el-table-column type="selection" width="55" align="center" />
            <el-table-column label="表的名称" align="center" prop="tableName" />
            <el-table-column label="文件名称" align="center" prop="fileName" />
            <el-table-column label="文件大小" align="center" prop="fileSize">
                <template slot-scope="scope">
                    {{ formatFileSize(scope.row.fileSize) }}
                </template>
            </el-table-column>
            <el-table-column label="数据库名称" align="center" prop="dbName" />

            <el-table-column label="操作" align="center" class-name="small-padding fixed-width" width="150">
                <template slot-scope="scope">
                    <el-button size="mini" type="text" icon="el-icon-download"
                        @click="handleDownload(scope.row)">下载</el-button>
                    <el-button size="mini" type="text" icon="el-icon-refresh-left"
                        @click="handleRecover(scope.row)">恢复</el-button>
                </template>
            </el-table-column>
        </el-table>

        <pagination v-show="total > 0" :total="total" :page.sync="queryParams.pageNum" :limit.sync="queryParams.pageSize"
            @pagination="getList" />


        <!-- 选择连接 -->

        <el-dialog title="恢复数据" :visible.sync="recoverVisible" width="800px" append-to-body :close-on-click-modal="false"
            v-dialogDrag>

            <el-form :model="recoverForm" :rules="recoverRules" ref="recoverForm" label-width="100px">
                <el-form-item label="连接名称" prop="connName">
                    <el-select style="width: 100%;" v-model="recoverForm.connName" placeholder="请选择连接名称"
                        @change="connChange">
                        <el-option v-for="item in connList" :key="item.id" :label="item.connName"
                            :value="item.connName"></el-option>
                    </el-select>
                </el-form-item>

                <el-form-item label="" v-if="!recoverSql() && recoverForm.connName != null">
                    <!-- 添加搜索功能 -->
                    <el-input v-model="tableSearch" placeholder="请输入表名称" clearable @keyup.enter.native="searchRecoveryTable"
                        style="width: 200px;"></el-input>
                    <el-button style="margin-left:10px" type="primary" @click="searchRecoveryTable">搜索</el-button>
                    <div style="margin-top: 10px;">
                    </div>
                </el-form-item>

                <!-- 这个是用于 -->
                <el-form-item label="恢复表" prop="tables" v-if="!recoverSql() && recoverForm.connName != null">

                    <!-- 表格显示表列表 添加多选 -->
                    <el-table highlight-current-row ref="multipleTable" :height="200" :data="tables" border
                        :row-key="(row) => row.tableName" style="width: 100%;" @selection-change="tableSelectChange">
                        <!-- 显示单选框 -->
                        <el-table-column type="selection" width="100" align="center" />
                        <el-table-column prop="tableName" label="表名称" align="center"></el-table-column>
                        <el-table-column prop="tableType" label="表类型" align="center"></el-table-column>
                    </el-table>
                </el-form-item>


                <!-- 显示恢复消息 -->
                <el-form-item label="执行日志" prop="log">
                    <el-input ref="recoveryMsgTextarea" type="textarea" v-model="recoverForm.log" :auto-rows="true" readonly
                        :rows="10"></el-input>
                </el-form-item>


            </el-form>
            <div slot="footer" class="dialog-footer">
                <el-button @click="recoverVisible = false">取消</el-button>
                <el-button type="primary" @click="handleRecoverSubmit" :loading="recoverLoading">恢复</el-button>
            </div>

        </el-dialog>




    </div>
</template>
  
<script>

import { listConn, getTableList, recovery, recoveryLastRowLog } from "@/api/db/conn";
import { addRecovery, getRecovery } from "@/api/db/recovery";

export default {
    name: "tablesFile",
    data() {
        return {
            // 表格高度
            tableHeight: document.documentElement.clientHeight - 180,
            // 遮罩层
            loading: true,
            // 选中数组
            ids: [],
            // 非单个禁用
            single: true,
            // 非多个禁用
            multiple: true,
            // 总条数
            total: 0,
            queryParams: {
                pageNum: 1,
                pageSize: 20,
                orderByColumn: "id",
                isAsc: "desc",
                connName: null,
                status: null,
            },
            recordList: [],
            allList: [],

            // 恢复数据
            recoverVisible: false,
            recoverForm: {
                log: '',
            },
            recoverRules: {},
            connList: [],
            tables: [],
            selectTableList: [],//选中的表列表
            recoverLoading: false,

            tableSearch: '',

        };
    },

    mounted() {
        this.initList();
    },
    watch: {
        'recoverForm.log': {
            handler(newValue) {
                this.$nextTick(() => {
                    const textarea = this.$refs.recoveryMsgTextarea.$el.firstChild;
                    if (textarea) {
                        textarea.scrollTop = textarea.scrollHeight;
                    }
                });
            },
            deep: true
        },
        'open': {
            handler(newValue) {
                if (newValue == false) {
                    clearTimeout(this.time1)
                }
            }
        }
    },

    computed: {
        issql() {
            return this.allList.length > 0 && this.allList[0].fileName.indexOf('sql') != -1;
        }
    },

    methods: {

        searchRecoveryTable() {

            this.connChange();

        },

        batchRecover() {
            this.recoverVisible = true;
            this.recoverForm = {
                log: '',
            }

        },
        batchDownload() {
            //批量下载
            let c = [...this.selectTableList];
            let param = c.map(item => item.fileAbsolutePath).join("#");
            this.download("/db/recovery/downloadBackupFile", {
                paths: param,
            }, `backup_${new Date().getTime()}.zip`);
        },

        // 恢复数据
        handleRecoverSubmit() {

            this.recoverLoading = true;

            let format = this.selectTableList[0].fileName.split('.')[1];
            let tables = null;
            if (format == 'sql') {
                tables = this.selectTableList.map(item => item.tableName).join("#");
            } else {
                tables = this.recoverForm.tables;
            }
            //添加到恢复表
            let aparam = {
                tables,
                connName: this.recoverForm.connName,
                dbName: this.recoverForm.dbName,
            }
            addRecovery(aparam).then((resp) => {
                // 恢复数据
                let c = [...this.selectTableList];
                c.forEach(item => {
                    item.recoveryConnName = this.recoverForm.connName;
                    if (format !== 'sql') {
                        item.tableName = tables;
                    }
                })
                let param = {
                    recoveryTables: c,
                    recoveryId: resp.data,
                }
                //执行恢复
                recovery(param).then(() => {
                    this.$message.success('恢复进行中...')
                }).catch(err => {
                    this.recoverLoading = false;
                    clearTimeout(this.time1);
                })
                //查询恢复进度
                this.getrecoveryLastRowLog(resp.data, 0);
            })
        },


        getrecoveryLastRowLog(recoveryId, cnt) {
            recoveryLastRowLog({
                recoveryId,
            }).then((resp) => {
                let msg = resp.msg;
                //添加日志
                if (msg.length > 0) {
                    msg += '\n';
                }
                this.recoverForm.log += msg;
                if (msg.indexOf('导入成功') !== -1) {
                    clearTimeout(this.time1);
                    this.$message.success('恢复完成')
                }
                this.time1 = setTimeout(() => {
                    cnt++;
                    if (cnt % 10 == 0) {
                        //判断是否结束 5s查询一次
                        getRecovery(recoveryId).then(response => {
                            if (response.data.endTime != null) {
                                clearTimeout(this.time1);
                                this.$message.success('恢复已结束')
                                this.recoverLoading = false;
                                this.recoverForm.log = response.data.logs;
                            } else {
                                this.getrecoveryLastRowLog(recoveryId, cnt);
                            }
                        });
                    } else {
                        this.getrecoveryLastRowLog(recoveryId, cnt);
                    }
                }, 100);
            });
        },


        tableSelectChange(selection) {
            console.log("选中的数据", selection);
            this.recoverForm.tables = selection.map(item => item.tableName).join("#");
            // 单选
            if (selection.length > 1) {
                this.$refs.multipleTable.clearSelection();
                this.$refs.multipleTable.toggleRowSelection(selection.pop());
            }
        },
        recoverSql() {
            return this.selectTableList.length > 0 && this.selectTableList[0].fileName.indexOf('sql') != -1
        },
        connChange(name) {

            //通过名字找到对应的dbName
            let conn = this.connList.find(item => item.connName == this.recoverForm.connName).connInfo.dbName;

            this.recoverForm.dbName = conn;
            return getTableList({
                connName: this.recoverForm.connName,
                tableName: this.tableSearch,
            }).then(response => {
                let c = response.data;
                let tables = c.map(item => {
                    return {
                        tableName: item.TABLE_NAME,
                        tableType: item.TABLE_TYPE
                    }
                });
                this.tables = tables;
            });
        },


        initList() {
            //查询所有的连接
            listConn({}).then(response => {
                this.connList = response.rows;
            })
        },


        formatFileSize(bytes, decimals = 2) {
            if (bytes === 0) return '0 Bytes';

            const k = 1024;
            const dm = decimals < 0 ? 0 : decimals;
            const sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];

            const i = Math.floor(Math.log(bytes) / Math.log(k));

            return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + ' ' + sizes[i];
        },
        setData(recordList, init = true) {
            this.loading = true;
            if (init) {
                this.allList = recordList;
            }
            this.total = recordList.length;

            //对recordList 按照pageNum*pageSize 进行分页
            let start = (this.queryParams.pageNum - 1) * this.queryParams.pageSize;
            let end = this.queryParams.pageNum * this.queryParams.pageSize;
            this.recordList = recordList.slice(start, end);
            this.loading = false;
        },
        // 多选框选中数据
        handleSelectionChange(selection) {
            this.ids = selection.map(item => item.id)
            this.single = selection.length !== 1
            this.multiple = !selection.length

            this.selectTableList = selection;
        },
        handleDownload(row) {
            //批量下载
            let c = [row];
            let param = c.map(item => item.fileAbsolutePath).join("#");
            this.download("/db/recovery/downloadBackupFile", {
                paths: param,
            }, `backup_${new Date().getTime()}.zip`, {
                timeout: 600000
            });

        },
        handleRecover(row) {
            //恢复文件
            this.recoverVisible = true;
            this.recoverForm = {
                log: '',
            }

            this.selectTableList = [row];

        },
        getList(data) {
            this.setData(this.allList, false);
        },

    }
};
</script>
  